
#! usr/bin/python

#-------------------------------------------------------------------------------
# Shrub's Python Intelligence Enhancing Game Engine Library
# or SPIEGEL (Named for Spike Spiegel)
# by Shrub
# v0.11
#-------------------------------------------------------------------------------

# Imports pygame to allow use of it's modules
import pygame
import pymunk

class ColourTables:
    """ColourTables is a class that defines the name
    of each colour and it's RGB value in a list"""
    def __init__(self):
        self.black = [  0,   0,   0]
        self.red   = [255,   0,   0]
        self.green = [  0, 255,   0]
        self.blue  = [  0,   0, 255]
        self.white = [255, 255, 255]


class SpiegelBase(object):
    """SpiegelBase is a set of functions that define
    a basic working game"""
    def __init__(self, size=(800, 600), bgcolour=[0,0,0], caption='SPIEGEL'):
        # Initialise pygame
        pygame.init()

        # Create window
        self.screen   = pygame.display.set_mode(size)
        pygame.display.set_caption(caption)
        self.screen.fill(bgcolour)

        # Draw screen
        pygame.display.flip()

        # Initialise sound
        pygame.mixer.init(48000)

        # Main game variables
        self.resolution = size
        self.clock      = pygame.time.Clock() #to track FPS
        self.size       = size
        self.fps        = 60
        self.mousepos   = pygame.mouse.get_pos()

        # Initialise pymunk
        self.space    = pymunk.Space()
        self.space.gravity = (0.0, 900.0)
        self.space._space.contents.elasticIterations = 10

        self.pymunk_list   = []
        
    def events(self):
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                self.running = False
            if event.type == pygame.KEYDOWN:
                self.key_down(event.key)
            if event.type == pygame.KEYUP:
                self.key_up(event.key)
            if event.type == pygame.MOUSEBUTTONUP:
                self.mouse_up(event.button, event.pos)
            if event.type == pygame.MOUSEBUTTONDOWN:
                self.mouse_down(event.button, event.pos)
            if event.type == pygame.MOUSEMOTION:
                self.mouse_motion(event.buttons, event.pos, event.rel)
    
    #wait until a key is pressed, then return
    def press_any_key(self):
        press = False
        while not press:
            for event in pygame.event.get():
                if event.type == KEYUP:
                    press = True
             
    #enter the main loop, possibly setting max FPS
    def game_loop(self, fps=0):
        self.running = True
        self.fps = fps
        
        while self.running:
            # Debug FPS thingy
            pygame.display.set_caption("FPS: %i" % self.clock.get_fps())

            # Runs three separate functions to govern the game's machinations
            # Only if the window is active
            if pygame.display.get_active:
                self.events()
                self.update()
                self.draw()

            # Constantly detect Mouse Co-ords
            self.mousepos = pygame.mouse.get_pos()

            pygame.display.flip()
            self.clock.tick(self.fps)

        pygame.quit()

    def resize_window(self, newres=(800, 600), fullscreen=False):
        """Newres should be a tuple"""
        if fullscreen:
            pygame.display.set_mode(newres, pygame.FULLSCREEN)
            pygame.transform.smoothscale(self.screen, newres)
        else:
            pygame.display.set_mode(newres)
            pygame.transform.smoothscale(self.screen, newres)

    def cursor_change(self, cursorshape, preset=0):
        """Cursor shape must be a string tuple of equal widths"""
        if preset:
            if preset == 'arrow':
                pygame.mouse.set_cursor(*pygame.cursors.arrow)
            if preset == 'reticule':
                thickarrow_strings = (
                    "   XX   ",
                    "   XX   ",
                    "   XX   ",
                    "XXX  XXX",
                    "XXX  XXX",
                    "   XX   ",
                    "   XX   ",
                    "   XX   ")
                pygame.mouse.set_cursor(
                                        pygame.cursor.compile(thickarrow_strings))
        else:
            thickarrow_strings = cursorshape
            pygame.mouse.set_cursor(
                                    pygame.cursor.compile(thickarrow_strings))

    def play_music(self, music_file):
        pygame.mixer.music.load(music_file)
        pygame.mixer.music.play(-1)

    def play_sound(self):
        pass
    
    """These empty functions are written over
    by the code you are using."""
    def update(self):
        """It's a good idea to place a couple of these
        code snippets in your update() method"""

        """
        This snippet checks if the window is active,
        It's a good idea to wrap it around your update code
        so that the game doesn't update when you're not playing.
        
        if pygame.display.get_active:
            <code>
        """
        pass
    
    def draw(self):
        pass
        
    def key_down(self, key):
        pass
        
    def key_up(self, key):
        pass
    
    def mouse_up(self, button, pos):
        pass

    def mouse_down(self, button, pos):
        pass

    def mouse_motion(self, buttons, pos, rel):
        pass

class Dialogue(object):
    """This is a class for making and displaying
    One or two person dialogue, with different
    options for displaying it in relation to objects
    or sprites, and screen relativity"""
    def __init__(self):
        pass
    def render_dialogue(self):
        pass

class ArbitraryFont(object):
    """This is a class to simplify the displaying
    of fonts for any purpose"""
    def __init__(self):
        pass


#-------------------------------------------------------------------------------
# Pymunk Stuff
#-------------------------------------------------------------------------------
class PymunkBall(object):
    def __init__(self, space, x=0, y=0, mass=1, radius=14):
        self.x             = x
        self.y             = y
        self.mass          = mass
        self.radius        = radius
        self.inertia       = pymunk.moment_for_circle(self.mass, 0, self.radius)
        self.body          = pymunk.Body(self.mass, self.inertia)
        self.body.position = self.x, self.y
        self.shape         = pymunk.Circle(self.body, self.radius)
        self.shape.elasticity = 0.35
        self.shape.friction   = 0.2
        self.shape.damping    = 0.999999
        space.add(self.body, self.shape)
        
    def draw(self, screen, ball):
        coords = int(ball.body.position.x), int(ball.body.position.y)
        pygame.draw.circle(screen, [255, 0, 0], coords, int(ball.radius), 2)
    
class PymunkLine(object):
    def __init__(self, space, x=700, y=500):
        self.x = x
        self.y = y
        self.body = pymunk.Body()
        self.body.position = (self.x, self.y)    
        self.line = pymunk.Segment(self.body, (-150, 0), (255.0, 0.0), 1.0)
        self.line.elasticity = 1.0

        space.add_static(self.line)

    def draw(self, screen, line):
        pygame.draw.line(screen, [255, 255, 255],
                         (line.body.position.x - 150, line.body.position.y),
                         (line.body.position.x + 255, line.body.position.y), 1)
